/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
package models;

import config.Models.Conf_Friend;
import db.Redis_Rd;
import db.Redis_W;
import java.util.List;
import java.util.Map;
import java.util.Set;
import entities.Friend;
import entities.User;
import java.util.ArrayList;
import java.util.HashMap;
import libCore.Util;
import org.json.simple.JSONValue;
import share.KeysDefinition;
import share.ShareMacros;

/**
 *
 * @author LinhTA
 */
public class U_FriendModel implements BaseModel {

    public String uId;
    public Map<String, Friend> fLists;

    public U_FriendModel(String uid) 
    {
        uId = uid;
        fLists = new HashMap<String, Friend>();
    }

    @Override
    public void setDB() 
    {
    }

    @Override
    public void setData(Map<String, String> obj) 
    {
    }

    @Override
    public void getDB(String uid) 
    {
        String keyFriends = KeysDefinition.getKey_ListFriends(uid);
        Set<String> fIds = Redis_Rd.getInstance().smember(keyFriends);

        List<String> friendIds = new ArrayList<String>( fIds );
        fLists = U_FriendModel.getFriends(friendIds);
    }

    public static U_FriendModel isNewUser(String uid) 
    {
        U_FriendModel friendModel = new U_FriendModel(uid);

        List<String> zmFriends  =   FakeData.getInstance().getFriendsList(uid);
        List<String> idFriends  =   new ArrayList<String>();
        
        for (int i = 0; i < zmFriends.size(); i++) {
            if ( !uid.equals(zmFriends.get(i)) && !UserModel.isNewUser(zmFriends.get(i)) ) 
            {
                String frIdReal =   zmFriends.get(i).toString();
                String id   =   uid + "_" + frIdReal;
                idFriends.add( frIdReal );
                
                Friend fr   =   new Friend();
                Map<String, String> val     =   Redis_Rd.getInstance().hget(KeysDefinition.getKeyUser( frIdReal ));
                fr.setDataUser(val);
                setFriendDB( id, frIdReal, fr );
                friendModel.fLists.put( frIdReal, fr );
            }
        }
        String[] keys   = idFriends.toArray( new String[idFriends.size()] );
        if ( idFriends.size() > 0 && Redis_W.getInstance().sadd(KeysDefinition.getKey_ListFriends(uid), keys ) != idFriends.size() ) 
        {
            return null;
        }

        return friendModel;
    }

    public static void setFriendDB( String fid, String id, Friend fr ) 
    {
        
        Map<String, Object> data    =   new HashMap<String, Object>();
        data.put( ShareMacros.FRIEND_ID, id);
        data.put( ShareMacros.HELP_FOOD, fr.helpfood );
        data.put( ShareMacros.STEAL_EGG, fr.stealegg );
        Redis_W.getInstance().set( fid, Util.obj2String(data) );
    }
    
    public static List<Integer> getZMFriends() 
    {
        //@@ chua dang ky App
        List<Integer> friendList = new ArrayList<Integer>();
        friendList.add(468598);
        return friendList;
    }

    public static Map<String, Friend> getFriends(List<String> friendIds) 
    {
        Map<String, Friend> map = new HashMap<String, Friend>();

        for (int i = 0; i < friendIds.size(); i++) 
        {    
            String id = friendIds.get(i);
//            Map<String, String> frStr   =   (Map<String, String>) JSONValue.parse(Redis_Rd.getInstance().get(id));
//            Map<String, String> val     =   Redis_Rd.hget(KeysDefinition.getKeyUser( frStr.get(ShareMacros.FRIEND_ID) ));
            Map<String, String> val     =   Redis_Rd.getInstance().hget(KeysDefinition.getKeyUser(id));

//            val.putAll( frStr );
            
            Friend f = new Friend();
            f.setDataUser( val );
            map.put(id, f);
        }

        return map;
    }

    public static Map<String, Friend> getAllFriendsData( String uid, List<String> friendIds ) 
    {
        Map<String, Friend> map = new HashMap<String, Friend>();

        for (int i = 0; i < friendIds.size(); i++) 
        {    
            String id = friendIds.get(i);
            Map<String, String> frStr   =   (Map<String, String>) JSONValue.parse(Redis_Rd.getInstance().get( uid + "_" + id ));
            Map<String, String> val     =   Redis_Rd.getInstance().hget(KeysDefinition.getKeyUser(id));

            val.putAll( frStr );
            
            Friend f = new Friend();
            f.setDataStr(val );
            map.put(id, f);
        }

        return map;
    }

    public Map<String, Object> toAMF() 
    {
        Map<String, Object> data = new HashMap<String, Object>();

        for (Map.Entry<String, Friend> f : fLists.entrySet()) {
            String string = f.getKey();
            Friend object = f.getValue();

            data.put(string, object.toAMF());
        }
        return data;
    }

    //======================= unknown =================
    
    public Friend getDataFriend(String fid) 
    {
        Friend f = new Friend();

        UserModel uModel    =   new UserModel( fid );
        User u = uModel.getDBUser();
        f.level = u.level;
        f.avata = u.avata;
        f.exp   = u.exp;
        f.gold  = u.gold;
        f.name  = u.name;

        return f;
    }

    public void getDBData() 
    {
        String keyFriends = KeysDefinition.getKey_ListFriends(uId);

        Set<String> slist = Redis_Rd.getInstance().smember(keyFriends);
        for (int i = 0; i < slist.size(); i++) {
            String fId = slist.toArray()[i].toString();
            Friend f = getDataFriend(fId);

            fLists.put(fId, f);
        }
    }
    
    public void setDataFriends(List<String> fids) 
    {
        for (int i = 0; i < fids.size(); i++) 
        {
            fLists.put(fids.get(i).toString(), getDataFriend(fids.get(i)));
        }
    }

    //================================ Hieu ==============================
    
    public Map<String, Object> getFriendList( String uid ) 
    {
        Map<String, Object> data;
        
        U_FriendModel ufriendModel =    new U_FriendModel(uid);
        String keyFriends = KeysDefinition.getKey_ListFriends(uid);
        Set<String> fIds = Redis_Rd.getInstance().smember(keyFriends);

        List<String> friendIds  =   new ArrayList<String>( fIds );
        ufriendModel.fLists     =   U_FriendModel.getAllFriendsData(uid, friendIds);
        data                    =   ufriendModel.toAMF();
        
        return data;
    }
    
    public Map<String, Object> getDataDetailFriend( String fid ) 
    {
        Map<String, Object> data    =   new HashMap<String, Object>();
        
        UserModel uModel    =   new UserModel( fid );
        User u  = uModel.getDBUser();
        data.put(ShareMacros.LEVEL, u.level);
        data.put(ShareMacros.FISH, u.fish);
        data.put(ShareMacros.GOLD, u.gold);
        data.put(ShareMacros.COIN, u.coin);
        data.put(ShareMacros.EXP, u.exp);
        data.put(ShareMacros.EXP, u.exp);
        data.put(ShareMacros.USER_NAME, u.name);
        data.put(ShareMacros.USER_AVATA, u.avata);

        U_CoteModel uCoteModel      =   new U_CoteModel( fid );
        uCoteModel.getDB( fid );
        data.put( ShareMacros.COTES, uCoteModel.toAMF() );
        
        return data;
    }
    
    /*
     * return: can help or not ?
     */
    public static Boolean helpFriendFood( String uid, String friendId, String coteId, int vFood ) 
    {
        Boolean result  =   false;
        
        UserModel uModel    =   new UserModel( uid );
        User u  =   uModel.getDBUser();
        // Update help friend in day
        Conf_Friend conf_friend =   config.ConfigModels.conf_friends;
        
        // Get friend model from user
        String strValueFr           =   Redis_Rd.getInstance().get( uid + "_" + friendId );
        Map<String, String> mValue  =   (Map<String, String>)JSONValue.parse( strValueFr );
        if( mValue == null || mValue.size() <= 0 )
            return false;
        
        String realId       =   mValue.get( ShareMacros.FRIEND_ID );
        int currentHelpFood =   Integer.parseInt( String.valueOf( mValue.get( ShareMacros.HELP_FOOD ) ));
        if( u.helpFood >= vFood && ( currentHelpFood + vFood ) <= conf_friend.maxFood )
        {
            // Increase friend food in cote
            U_CoteModel coteModel   =   new U_CoteModel( realId );
            result  =   coteModel.dropFish( coteId, vFood );

            u.helpFood      -=  vFood;
            currentHelpFood +=  vFood;
            
            mValue.put( ShareMacros.HELP_FOOD, String.valueOf( currentHelpFood ));
            
            Redis_W.getInstance().set( friendId, Util.obj2String( mValue ) );
        }
        
        return result;
    }
    
    /*
     * return: value of egg was stolen
     */
    public static int stealFriendEgg( String uid, String friendId, String coteId, String eggId ) 
    {
        int eggValue    =   0;
        
        UserModel uModel    =   new UserModel( uid );
        User u  =   uModel.getDBUser();
        // Update help friend in day
        Conf_Friend conf_friend =   config.ConfigModels.conf_friends;
        
        // Get friend model from user
        String strValueFr           =   Redis_Rd.getInstance().get( uid + "_" + friendId );
        Map<String, String> mValue  =   (Map<String, String>)JSONValue.parse( strValueFr );
        if( mValue == null || mValue.size() <= 0 )
            return -1;
        
        String realId       =   mValue.get( ShareMacros.FRIEND_ID );
        int currentStealEgg =   Integer.parseInt( String.valueOf( mValue.get( ShareMacros.STEAL_EGG ) ));
        if( ( currentStealEgg + 1 ) <= conf_friend.maxEgg )
        {
            // try to sell egg in friend cote but send gold to current user
            U_CoteModel coteModel   =   new U_CoteModel( realId );
            eggValue        =   coteModel.stealEgg( coteId, eggId );

            currentStealEgg +=  1;
            
            mValue.put( ShareMacros.STEAL_EGG, String.valueOf( currentStealEgg ));
            
            Redis_W.getInstance().set( friendId, Util.obj2String( mValue ) );
        }
        return eggValue;
    }
    
    //================================ Hieu ==============================
    
}